<template>
    <div>
        <div id="map" class="map" ref="rootmap" v-loading="loading">
        </div>
        <el-row :gutter="22">
            <el-col :span="3">
              <el-button type="primary" @click="getDemoLayer">加载选区</el-button>
            </el-col>
            <el-col :span="2" v-if="canDel">
              <el-button type="primary" @click="delBatch">删除</el-button>
            </el-col>
          <el-col :span="2">
              <el-button type="primary" @click="drawPolygon">绘制</el-button>
          </el-col>
          <el-col :span="2">
              <el-button type="primary" @click="undo">撤回</el-button>
          </el-col>
          <el-col v-if="canSave" :span="2">
              <el-button type="primary" @click="save">保存</el-button>
          </el-col>
            <el-col :span="2" v-if="canUnion"><el-button type="primary" @click="union">合并</el-button></el-col>
            <el-col :span="2" v-if="canSplit"><el-button type="primary" @click="split">拆分</el-button></el-col>
            <el-col :span="6">
                <el-button v-if="canCut" type="primary" @click="cutDraw('Polygon')">擦除</el-button>
                <el-button v-if="canCut" type="primary" @click="cutDraw('LineString')">剪切</el-button>
                <el-button v-if="okCut" type="primary" @click="cut">提交</el-button>
            </el-col>
        </el-row>
        <br>
        <el-row :gutter="20">
            <el-col :span="2">
                <el-select v-model="zoom" placeholder="请选择放缩" @change="center">
                  <el-option label="省" value="7">省</el-option>
                  <el-option label="市" value="9">市</el-option>
                  <el-option label="区" value="11">区</el-option>
                  <el-option label="镇" value="13">镇</el-option>
                </el-select>
            </el-col>
            <el-col :span="2">
                
            </el-col>
        </el-row>
    </div>

</template>

<script>
import { Map, View } from "ol";
import {Tile as TileLayer, Vector as VectorLayer} from 'ol/layer';
import Modify from 'ol/interaction/Modify';
import Draw from 'ol/interaction/Draw';
import VectorSource from 'ol/source/Vector';
import Snap from 'ol/interaction/Snap';
import WKT from 'ol/format/WKT';
import { featuresToWKTs } from '@/api/util'
import { saveGeoms,geoJson,unionGeos,splitGeos,cutGeos,delBatch,getCenter,pageList } from '@/api/demo'
import "ol/ol.css";
import GeoJSON from 'ol/format/GeoJSON';
import {Fill, Stroke, Style} from 'ol/style';
import TileWMS from 'ol/source/TileWMS';
import OSM from 'ol/source/OSM';
import XYZ from 'ol/source/XYZ';
import {fromLonLat} from 'ol/proj';

export default{
    
    data(){
        return{
            apiKey: '48847924576b6e10c69f02b80ab5b8b2',
            map: {},// 地图
            filter:{
                levels: 1,
                shengName: '广东省',
                shiName: '',
                xianName: '',
                code: '44'
            },
            draw:null,//绘制
            centerPoint: [],// 中心点
            zoom: 7,// 放大
            vectorSource: {},// 绘制source
            vectorLayer: {},// 绘制图层
            zqLayer: {}, // 政区图层
            canSave:false,// 费否可以保存绘制
            canUnion:false,// 是否可以合并
            layers:[],// 初始化图层
            modify:{},// 修改
            snap:{},// 修改
            geojson:{},// 操作图层
            select:{},// 选择
            selected: [],// 选中
            canSplit: false,// 是否可以拆分
            myLayerId: -1,// 操作图层ID
            drawLayerId: -1,// 绘制图层ID
            drawCut:null,//裁剪
            cutSource:null,// 裁剪Source
            canCut: false,// 是否可以裁剪
            okCut: false,// 是否可以提交裁剪
            canDel:false,// 是否可以删除
            canSelect: true,// 是否可以选择
            cutLayer:null,// 裁剪图层
            cutFeatures:[],// 裁剪Features
            loading:false// 请求时加载
        };
    },
    watch:{
        // 判断选中的值
        selected: function(value){
            // 过滤选中的脏数据
            let filter = value.filter(e=>typeof e.getProperties().id == 'number')
            // console.log(filter[0].getGeometry().getType())
            // 如果只有一个MultiPolygon
            if(filter.length==1 && filter[0].getGeometry().getType() == 'MultiPolygon'){
                this.canSplit = true
                this.canCut = true
            }else{
                this.canSplit = false
            }
            // 裁剪状态控制
            if(filter.length==1){
                this.canCut = true
            }
           if(filter.length == 0 || filter.length > 1){
                this.canCut = false
           }
           // 合并状态控制
           if(filter.length>1){
               this.canUnion = true
           }else{
               this.canUnion = false
           }
           // 删除状态控制
           if(filter.length>0){
               this.canDel = true
           }else{
               this.canDel = false
           }
        },
        draw: function(value){
            // 保存状态控制
            if(value==null){
                this.canSave = false
            }else{
                this.canSave = true
            }
        }
    },
    created(){
        this.initMap()
        this.center()
    },
    mounted(){
     this.initMap()
    },
    methods:{
        //绘图
        drawPolygon(){
            //初始化绘制图层
            this.vectorSource = new VectorSource({
                wrapX: false,
                features:this.features,
                projection: "EPSG:4326"
            });
            this.vectorLayer = new VectorLayer({
                source: this.vectorSource,
                projection: "EPSG:4326"
            })
            this.drawLayerId = this.vectorLayer.ol_uid
            // 添加当前绘制图形
            this.map.addLayer(this.vectorLayer)
            //先清空之前的操作
            this.map.removeInteraction(this.draw)
            if(this.type!='None'){
                this.draw = new Draw({
                    source: this.vectorSource,//绘制图层的元数据
                    type: 'Polygon'// 绘制的类型
                })
                // 当前地图添加绘制函数
                this.map.addInteraction(this.draw)
            }
        },
         // 取消最后一次操作
        undo(){
            this.draw.removeLastPoint()
        },
        //保存
        save(){
            this.loading = true
            // 保存时清除绘制图层
            this.map.removeLayer(this.vectorLayer);
            this.vectorLayer = null;
            // 清除绘制
            this.map.removeInteraction(this.draw)
            this.draw = null
            // 清除选择
            this.selected = []
            // 获取画的图
            let geo = this.vectorSource.getFeatures()
            // 转换成WKT
            let resobj = featuresToWKTs(geo)
            let geos = []
            resobj.polygon.forEach(geo => {
                geos.push({geometry:geo})
            });
            let g = JSON.stringify(geos)
            saveGeoms(g).then(res=>{
                this.resNotify(res)
                // 重新加载图层
                this.getDemoLayer()
            }).catch(e=>{
                this.$notify({
                    title: '错误',
                    message: e,
                    type: 'error'
                })
            }).finally(()=>{
                this.loading = false
            })
        },
        // 创建数据库图层
        getDemoLayer(){
            this.loading = true
            // 清空选区
            this.selected = []
            // 清空修改
            this.map.removeInteraction(this.modify)
            this.map.removeInteraction(this.snap)
            // // 分页
            // let page = { "current":1, "size":10 }
            // 获取分页geojson数据
            geoJson().then(res=>{
                this.geojson = JSON.parse(res.data.data)
                let data = '{"type":"FeatureCollection","crs":{"type":"name","properties":{"name":"EPSG:4326"}},"features":[],"properties":[]}'
                if(this.geojson.features==null){
                    this.geojson = JSON.parse(data)
                }
                // 数据源选择后端的
                const vectorSource = new VectorSource({
                    features: new GeoJSON().readFeatures(this.geojson)
                });
                // 图层
                const vectorLayer = new VectorLayer({
                    source: vectorSource
                });

                    // 定义修改
                this.modify = new Modify({
                    source: vectorSource
                })
                //定义Snap 
                this.snap = new Snap({
                    source: vectorSource
                })
                this.hasMyLayer(vectorLayer)
                // 添加修改到map
                this.map.addInteraction(this.modify)
                this.map.addInteraction(this.snap)
                this.map.addLayer(vectorLayer);
            }).catch(e=>console.log(e)).finally(()=>{
                this.loading = false
            })       
        },
        // 合并
        union(){
            this.loading = true
            let saveObjList = []
            // 过滤脏数据
            let filter = this.selected.filter(e=>typeof e.getProperties().id == 'number')
            let len = filter.length
            for(let i = 0; i < len; i++){
                // let geoZqDemo = {id:this.selected[i].getPropties(),}
                let id = filter[i].getProperties().id
                saveObjList.push(id)
            }
            unionGeos(saveObjList).then(res=>{
                this.resNotify(res)
                this.getDemoLayer()
            }).catch(e=>{
                this.$notify({
                    title: '错误',
                    message: e,
                    type: 'error'
                })
            }).finally(()=>{
                this.loading = false
            })
        },
        // 拆分
        split(){
            this.loading = true
            let filter = this.selected.filter(e=>typeof e.getProperties().id == 'number')
            splitGeos(filter[0].getProperties().id).then(res=>{
                this.resNotify(res)
                if(res.data.code == 'OK'){
                    this.getDemoLayer()
                }
            }).catch(e=>{
                this.$notify({
                    title: '错误',
                    message: e,
                    type: 'error'
                })
            }).finally(()=>{
                this.loading = false
            })
        },
        // 剪裁绘制
        cutDraw(type){
            this.canSelect = false
            // 移除之前的
            if(this.cutLayer!=null){
                this.map.removeLayer(this.cutLayer)
                this.cutLayer = null
            }
            if(this.drawCut!=null){
                this.map.removeInteraction(this.drawCut)
                this.drawCut = null
            }
            //初始化绘制图层
            this.cutSource = new VectorSource({
                wrapX: false,
                features:this.features,
                projection: "EPSG:4326"
            });
            this.cutLayer = new VectorLayer({
                source: this.cutSource,
                projection: "EPSG:4326"
            }); 
            // 添加图层到 map
            this.map.addLayer(this.cutLayer)
            this.drawCut = new Draw({
                source: this.cutSource,//绘制图层的元数据
                // type: 'Polygon'// 绘制的类型
                type: type// 绘制的类型
            })
            // 当前地图添加绘制函数
            this.map.addInteraction(this.drawCut)
            this.canCut = false
            this.okCut = true
        },
        // 提交裁剪
        cut(){
            // 过滤脏数据
            let filter = this.selected.filter(e=>typeof e.getProperties().id == 'number')
            // 被剪裁ID
            let cutId = filter[0].getProperties().id
            // features
            let features = this.cutSource.getFeatures()
            // cutGeoWkt
            let cutGeoWkt = new WKT().writeFeature(features[0])
            // dto
            let dto = {cutGeoWkt:cutGeoWkt,cutId:cutId}
            cutGeos(dto).then(res=>{
                this.loading = true
                this.resNotify(res)
                // 清除绘制
                if(this.cutLayer!=null){
                this.map.removeLayer(this.cutLayer)
                this.cutLayer = null
            }
                if(this.drawCut!=null){
                    this.map.removeInteraction(this.drawCut)
                    this.drawCut = null
                }
                // 修改状态
                this.okCut = false
                this.getDemoLayer()
            }).catch(e=>{
                this.$notify({
                    title: '错误',
                    message: e,
                    type: 'error'
                })
            }).finally(()=>{
                this.canSelect = true
                this.loading = false
            })
        },
        //批量删除
        delBatch(){
            this.loading = true
            // 过滤脏数据
            let filter = this.selected.filter(e=>typeof e.getProperties().id == 'number')
            let delIds = []
            filter.forEach(e=>{delIds.push(e.getProperties().id)})
            delBatch(delIds).then(res=>{
                this.resNotify(res)
                this.getDemoLayer()
            }).catch(e=>{
                this.$notify({
                    title: '错误',
                    message: e,
                    type: 'error'
                })
            }).finally(()=>{
                this.loading = false
            })
        },
        // 初始化
        initMap(){
            this.loading = true
            this.map = null;
            let _this = this;
                // 卫星图层
            let wx = new TileLayer({//卫星
                source: new OSM()
            })
            // 行政
            this.zqLayer = new TileLayer({//行政
                source: new TileWMS({
                    // url: 'http://localhost:8081/geoserver/nyc/wms',
                    url: 'http://localhost:8081/geoserver/zq/wms',
                    params:{
                        "LAYERS": 'zq:geo_zq',
                        "CQL_FILTER":"levels="+this.filter.levels,
                    },
                    projection: "EPSG:4326",
                    serverType: 'geoserver'
                })
            })
                    // this.layers.push(new TileLayer({//路网
        // opacity: 0.8,
        //     source: new XYZ({
        //         url: "http://t4.tianditu.com/DataServer?T=vec_w&x={x}&y={y}&l={z}&tk=48847924576b6e10c69f02b80ab5b8b2",
        //         projection: "EPSG:3857"
        //     })
        // }))
         
        // this.layers.push(new TileLayer({//行政
        //     source: new TileWMS({
        //         // url: 'http://localhost:8081/geoserver/nyc/wms',
        //         url: 'http://localhost:8081/geoserver/zq/wms',
        //         params:{
        //             "LAYERS": 'zq:geo_zq'
        //             // "LAYERS": '	nyc:blocks'
        //         },
        //         projection: "EPSG:4326",
        //         serverType: 'geoserver'
        //     })
        // }))
            // 文字标注
            // this.layers.push(new TileLayer({// 文字
            //     source: new XYZ({
            //         url: 'http://t3.tianditu.com/DataServer?T=cva_w&x={x}&y={y}&l={z}&tk=befa0939e3a58f616f539562541ee190',
            //         projection: "EPSG:4326"
            //     })
            // }))

            this.layers.push(wx)
            this.layers.push(this.zqLayer)

            // 初始化
            this.map = new Map({
                target: 'map',
                layers: this.layers,
                view: new View({
                    center: [110, 30],
                    zoom: 5,
                    projection: 'EPSG:4326'
                })
            });

            this.selected = []
            
            // 样式
            const highlightStyle = new Style({
                fill: new Fill({
                    color: '#EEE',
                }),
                stroke: new Stroke({
                    color: '#3399CC',
                    width: 2,
                }),
            });
            // 监听点击
            this.map.on('click',function(e){
                if(_this.canSelect){
                    _this.map.forEachFeatureAtPixel(e.pixel, function (f) {
                    const selIndex = _this.selected.indexOf(f);
                    if (selIndex < 0) {
                    _this.selected.push(f);
                    f.setStyle(highlightStyle);
                    } else {
                    _this.selected.splice(selIndex, 1);
                    f.setStyle(undefined);
                    }
                });
                }
            })
            this.loading = false
        },
        // 设置中心点
        center(){
            this.loading = true
            // 设置显示级数
            this.setLevels(this.zoom)
            // 获取中心
            getCenter(this.filter.code).then(res=>{
                // 设置中心点
                if(res.data.code=='OK'){
                    let centerObj = res.data.data
                    this.centerPoint.push(centerObj.x)
                    this.centerPoint.push(centerObj.y)
                    // 设置中心点
                    this.map.getView().setCenter(fromLonLat(this.centerPoint, 'EPSG:4326'))
                    // 放大 
                    this.map.getView().setZoom(this.zoom)
                }else{
                    this.$notify({
                        title: '错误',
                        message: '获取中心点失败',
                        type: 'error'
                    })
                }
            }).catch(e=>console.log(e)).finally(()=>{
                this.loading = false
            })
            // this.map.getView().setCenter()
        },
        //提示返回信息
        resNotify(res){
            if(res.data.code=="OK"){
                    this.$notify({
                        title: '成功',
                        message: res.data.data,
                        type: 'success'
                    })
                }else{
                    this.$notify({
                        title: '失败',
                        message: res.data.data,
                        type: 'error'
                    })
                }
        },
        // 当前是否有自己的图层
        hasMyLayer(vectorLayer){
            // 判断当前是否有自己的图层
                if(this.myLayerId != -1){
                    // 有 删除再添加
                    let layers = this.map.getAllLayers()
                    layers.forEach(layer=>{
                        if(layer.ol_uid==this.myLayerId){
                            this.map.removeLayer(layer)
                        }
                    })
                }
                this.myLayerId = vectorLayer.ol_uid
        },
        setLevels(value){
            if(value==7){
                this.filter.levels = 1
            }else if(value==9){
                this.filter.levels = 2
            }else if(value==11){
                this.filter.levels = 3
            }else{
                this.filter.levels = 4
            }
            let params = {
                        "LAYERS": 'zq:geo_zq',
                        "CQL_FILTER":"levels="+this.filter.levels,
            }
            this.zqLayer.getSource().updateParams(params)
        }
        
    }
}
</script>
<style>
    .map {
        height: 500px;
        width: 80%;
    }
</style>
